package com.yerbamateprimer.round;

import java.io.Serializable;
import java.util.List;

import com.yerbamateprimer.action.user.UserAction;
import com.yerbamateprimer.model.Group;
import com.yerbamateprimer.model.Mate;
import com.yerbamateprimer.model.User;
import com.yerbamateprimer.round.state.State;
import com.yerbamateprimer.round.state.StateName;

/**
 * This interface defines
 * a yerba mate round.
 * 
 * @author Matias Liwski
 * @version 1.0
 */
public interface Round extends Serializable{
	/**
	 * @return The list of participants that are at penance for this round.
	 */
	List<User> getPenanceParticipants();

	/**
	 * @param user A user to add to the penance list.
	 */
	void putUserInPenance(User user);

	/**
	 * @param user A user to remove from penance list.
	 */
	void releaseUserFromPenance(User user);

	/**
	 * @param user The user to invite to the round.
	 */
	void inviteUser(User user);

	/**
	 * @param group The group to invite to the round.
	 */
	void inviteGroup(Group group);

	/**
	 * @return The list of invited users.
	 */
	List<User> getInvitedUsers();

	/**
	 * @param user The user to confirm as drinker.
	 */
	void confirmUser(User user);

	/**
	 * @param user The user to remove from the round (No matter if it's on drinkers or invited list ).
	 */
	void removeUser(User user);

	/**
	 * @return The users participating in this round.
	 */
	List<User> getDrinkers();

	/**
	 * @param user Set the current drinker of the mate.
	 */
	void setCurrentDrinker(User user);

	/**
	 * @return The current drinker of the mate, or null if none.
	 */
	User getCurrentDrinker();

	/**
	 * @param action The last action that a user wants to execute, to set.
	 */
	void setLastIntendedAction(UserAction action);

	/**
	 * @return The last action that a user wants to execute.
	 */
	UserAction getLastIntendedAction();

	/**
	 * @return The next drinker of the yerba mate, or null if none.
	 */
	User rotateCurrentDrinker();

	/**
	 * @param user The primer of the mate for this round, to set.
	 */
	void setPrimer(User user);

	/**
	 * @return The primer of the mate for this round.
	 */
	User getPrimer();

	/**
	 * @param mate The yerba mate to use in this round, to set.
	 */
	void setMate(Mate mate);

	/**
	 * @return The mate in use for this round.
	 */
	Mate getMate();

	/**
	 * @return The state of this round.
	 */
	State getCurrentState();

	/**
	 * @param state The state of this round, to set.
	 */
	void setCurrentState(State state);

	/**
	 * @param state A possible state of this round, to add.
	 */
	void addState(State state);
	
	/**
	 * @param stateName The state name of the state that want to get.
	 * @return The state with the provided name state. 
	 */
	State getState(StateName stateName);

	/**
	 * @return The list of possible states for this round.
	 */
	List<State> getStates();

	/**
	 * Reset the rounds to his building state, and "clear" all the fields.
	 */
	void resetRound();
}